package com.winit.cloudlink.mgmt.recovery;

import com.google.common.collect.Maps;
import com.google.common.io.Files;
import com.winit.cloudlink.Cloudlink;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.time.FastDateFormat;
import org.springframework.amqp.rabbit.connection.ConnectionFactory;
import org.springframework.beans.factory.annotation.Autowired;

import java.io.File;
import java.io.IOException;
import java.util.Date;
import java.util.Map;

@Slf4j
public class MessageBackupTaskManagerImpl implements MessageBackupTaskManager {
    public static final String separator = "_";
    public static final String fileExtension = ".log";
    private FastDateFormat df = FastDateFormat.getInstance("yyyy-MM-dd");

    @Autowired
    private Cloudlink cloudlink;
    @Autowired
    private ConnectionFactory connectionFactory;
    @Autowired
    private RecoveryProperties recoveryProperties;

    private Map<String, MessageBackupTask> backupTasks = Maps.newConcurrentMap();


    @Override
    public String startBackupTask(String queueName) {
        MessageBackupTask backupTask = backupTasks.get(queueName);
        if (backupTask != null) {
            String msg = String.format("队列'%s'正在备份到文件'%s'中，无需再次执行.", queueName, backupTask.getBackupFile());
            log.warn(msg);
            throw new MessageBackupException(msg);
        }
        try {
            String childDir = cloudlink.getMetadata().getCurrentZone().getName();
            String backupFile = getBackupFile(recoveryProperties.getBackupDir(), childDir, queueName);
            MessageBackupTask backup = new MessageBackupTask(connectionFactory, queueName, backupFile);
            backup.execute();
            backupTasks.put(queueName, backup);
            return backupFile;
        } catch (Exception e) {
            String msg = String.format("备份队列'%s'出错", queueName);
            log.error(msg, e);
            throw new MessageBackupException(msg);
        }
    }

    @Override
    public void stopBackupTask(String queueName) {
        log.info("停止备份队列'{}'里的消息.", queueName);
        MessageBackupTask backupTask = backupTasks.get(queueName);
        if (backupTask != null) {
            backupTask.stop();
            backupTasks.remove(queueName);
        }
    }


    protected String getBackupFile(String parentDir, String childDir, String queueName) throws IOException {
        String baseDir = parentDir.endsWith(File.separator) ? parentDir + childDir : parentDir + File.separator + childDir;
        String suffix = df.format(new Date());
        String logFilename = queueName + separator + suffix;
        File logFile = new File(baseDir, logFilename + fileExtension);
        if (!logFile.exists()) {
            Files.createParentDirs(logFile);
            return logFile.getAbsolutePath();
        }
        int index = 0;
        do {
            index++;
            logFilename = queueName + separator + suffix + separator + index;
            logFile = new File(baseDir, logFilename + fileExtension);
        } while (logFile.exists());
        Files.createParentDirs(logFile);
        return logFile.getAbsolutePath();
    }
}
